package SingletonPattern

import "sync"

/*
单例模式：分为 饿汉模式、懒汉模式
饿汉模式：是在全局的单例实例在包被加载的时候创建
懒汉模式：是全局的单例实例在第一次使用时被创建
*/

type singleton struct {
}

//包被加载时创建实例
var instance *singleton = new(singleton)

// GetInsOr
// @author: lhg
// @Date: 2021-08-11 11:37:50
// @Description: 获取实例
// @return *singleton
//
func GetInsOr() *singleton {
	return instance
}

/*******************懒汉模式*******************/
//
var ins *singleton

// GetInstance
// @author: lhg
// @Date: 2021-08-11 11:36:14
// @Description: 获取实例（非并发安全）
// @return *singleton
//
func GetInstance() *singleton {
	if ins == nil {
		ins = new(singleton)
	}
	return ins
}

var mu sync.Mutex

// GetInstance1
// @author: lhg
// @Date: 2021-08-11 11:40:09
// @Description: 加锁确保并发安全
// @return *singleton
//
func GetInstance1() *singleton {
	if ins == nil {
		mu.Lock()
		if ins == nil {
			ins = new(singleton)
		}
		mu.Unlock()
	}
	return ins
}

var once sync.Once

// GetInstance2
// @author: lhg
// @Date: 2021-08-11 11:41:30
// @Description: 最佳实践，采用Once确保实例只被初始化一次,并且当存在多个线程调用该方法是也能保证只执行一次
// @return *singleton
//
func GetInstance2() *singleton {
	once.Do(func() {
		ins = new(singleton)
	})
	return ins
}
